package com.banmao.snake_client.netty.handler;

import com.banmao.snake_core.netty.Myinterface.ResponseHandlerPromise;
import com.banmao.snake_core.netty.message.impl.LoginRequestMessage;
import com.banmao.snake_core.netty.message.impl.LoginResponseMessage;
import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.util.concurrent.DefaultPromise;
import io.netty.util.concurrent.Promise;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Component;

import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.TimeUnit;

@Slf4j
@Component
public class LoginResponseHandler extends SimpleChannelInboundHandler<LoginResponseMessage> {

    //                       序号      用来接收结果的 promise 对象
    public static final Map<String, Promise<LoginResponseMessage>> PROMISES = new ConcurrentHashMap<>();

    @Override
    protected void channelRead0(ChannelHandlerContext channelHandlerContext, LoginResponseMessage loginResponseMessage) throws Exception {
        log.debug("{}", loginResponseMessage);
        // 拿到空的 promise
        Promise<LoginResponseMessage> promise = PROMISES.remove(loginResponseMessage.getSequenceId());
        if (promise != null) {
            Object returnValue = loginResponseMessage.getResponse();
            Throwable exceptionValue = loginResponseMessage.getThrowable();
            if(exceptionValue != null) {
                promise.setFailure(exceptionValue);
            } else {
                promise.setSuccess(loginResponseMessage);
            }
        }
    }

    public static Promise<LoginRequestMessage> makePromise(LoginRequestMessage msg, Channel channel) {
        try {
            // 用 Promise 接收响应结果
            DefaultPromise<LoginResponseMessage> promise = new DefaultPromise<>(channel.eventLoop());
            LoginResponseHandler.PROMISES.put(msg.getSequenceId(), promise);

            promise.await(10, TimeUnit.SECONDS);
            if(promise.isSuccess()) {
                // 调用正常
                LoginResponseMessage responseMessage = promise.getNow();
                if(responseMessage.isSuccess()) {
                    log.info("登陆成功 response:{}", responseMessage.getResponse());
                } else {
                    log.info("登陆失败 error: {}", responseMessage.getCause());
                }
            } else {
                // 调用失败
                Throwable cause = promise.cause();
                log.error("promise cause: {}", cause.getCause(), cause);
            }
            return null;
        } catch (InterruptedException e) {
            throw new RuntimeException(e);
        }
    }
}
